25. PowerShell pipeline

Note

The below information is extensively based in information taken from the PowerShell® Notes for Professionals book. I plan to extend this information based on my day to day usage of the language.

PowerShell introduces an object pipelining model, which allows you to send whole objects down through the pipeline to consuming commandlets or (at least) the output. In contrast to classical string-based pipelining, information in piped objects don't have to be on specific positions. Commandlets can declare to interact with

Objects from the pipeline as input, while return values are sent to the pipeline automatically.

25.1: Writing Functions with Advanced Lifecycle

This example shows how a function can accept pipelined input, and iterate efficiently.

Note, that the begin and end structures of the function are optional when pipelining, but that process is required when using ValueFromPipeline or ValueFromPipelineByPropertyName.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
function Write-FromPipeline{
  [CmdletBinding()]
  param(
    [Parameter(ValueFromPipeline)]
    $myInput
  )
  begin {
    Write-Verbose -Message "Beginning Write-FromPipeline"
  }
  process {
    Write-Output -InputObject $myInput
  }
  end {
    Write-Verbose -Message "Ending Write-FromPipeline"
  }
}

$foo = 'hello','world', 1 , 2 , 3

$foo | Write-FromPipeline -Verbose

Output:

1
2
3
4
5
6
7
VERBOSE: Beginning Write-FromPipeline
hello
world
1
2
3
VERBOSE: Ending Write-FromPipeline

25.2: Basic Pipeline Support in Functions

This is an example of a function with the simplest possible support for pipelining.

Any function with pipeline support must have at least one parameter with the ParameterAttribute

ValueFromPipeline or ValueFromPipelineByPropertyName set, as shown below.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
function Write-FromPipeline {
  param(
    [Parameter(ValueFromPipeline)] # This sets the ParameterAttribute
    [String]$Input
  )
  Write-Host $Input
}

$foo = 'Hello World!'

$foo | Write-FromPipeline

Output:

Hello World!

Note: In PowerShell 3.0 and above, Default Values for ParameterAttributes is supported. In earlier versions, you must specify ValueFromPipeline=$true.

25.3: Working concept of pipeline

In a pipeline series each function runs parallel to the others, like parallel threads. The first processed object is transmitted to the next pipeline and the next processing is immediately executed in another thread. This explains the high speed gain compared to the standard ForEach

1
@( bigFile_1, bigFile_2, ..., bigFile_n) | Copy-File | Encrypt-File | Get-Md5
  1. step - copy the first file (in Copy-file Thread)
  2. step - copy second file (in Copy-file Thread) and simultaneously Encrypt the first (in Encrypt-File)
  3. step - copy third file (in Copy-file Thread) and simultaneously encrypt second file (in Encrypt-File) and simultaneously get-Md5 of the first (in Get-Md5)